package com.psedu.base.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.psedu.base.constant.Constants;
import com.psedu.base.domain.Apply;
import com.psedu.base.domain.Semester;
import com.psedu.base.domain.SemesterDept;
import com.psedu.base.domain.vo.MergeDeptInfo;
import com.psedu.base.domain.vo.SemesterDeptVo;
import com.psedu.base.domain.vo.SaveMergeClassVo;
import com.psedu.base.mapper.ApplyMapper;
import com.psedu.base.mapper.SemesterDeptMapper;
import com.psedu.base.mapper.SemesterMapper;
import com.psedu.base.service.MergeClassService;
import com.psedu.common.core.constant.SecurityConstants;
import com.psedu.common.core.domain.R;
import com.psedu.system.api.RemoteDeptService;
import com.psedu.system.api.domain.vo.SysSimpleDeptVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

@Service
public class MergeClassServiceImpl implements MergeClassService {

    @Autowired
    private SemesterDeptMapper semesterDeptMapper;

    @Autowired
    private RemoteDeptService remoteDeptService;

    @Autowired
    private ApplyMapper applyMapper;

    @Autowired
    private SemesterMapper semesterMapper;

    /**
     * 获取学期分班
     * @param semeId 学期ID
     * @return 分班情况
     */
    @Override
    public MergeDeptInfo getMergeDeptInfo(Long semeId) {
        // 需要填充分分班信息
        MergeDeptInfo mergeDeptInfo = new MergeDeptInfo();

        // 学期名称
        Semester semester = semesterMapper.selectById(semeId);
        mergeDeptInfo.setTrainName(semester.getSemeName());

        // 学期下的所有分党校
        List<SemesterDeptVo> semesterDeptVos = semesterDeptMapper.selectVoList(
                new LambdaQueryWrapper<SemesterDept>()
                        .eq(SemesterDept::getSemeId, semeId),
                SemesterDeptVo.class
        );

        // 填充合班信息
        List<SemesterDeptVo> waitDeptList = new ArrayList<>();
        List<List<SemesterDeptVo>> mergeClassList = new ArrayList<>();
        for(int i = 0; i < Constants.MERGE_CLASS_COUNT; i++) {
            mergeClassList.add(new ArrayList<SemesterDeptVo>());
        }
        mergeDeptInfo.setWaitDeptList(waitDeptList);
        mergeDeptInfo.setMergeClassList(mergeClassList);

        // 查远程部门名称
        List<Long> deptIds = semesterDeptVos.stream().map(SemesterDeptVo::getDeptId).collect(Collectors.toList());
        R<List<SysSimpleDeptVo>> deptRes = remoteDeptService.getDeptNameByDeptId(deptIds, SecurityConstants.INNER);
        List<SysSimpleDeptVo> deptList = deptRes.getData();

        // 填充报名数量，排除没人报名的分党校
        semesterDeptVos = semesterDeptVos.stream().filter(semesterDeptVo -> {
            Long studentCount = applyMapper.selectCount(
                    new LambdaQueryWrapper<Apply>()
                            .eq(Apply::getDeptId, semesterDeptVo.getDeptId())
                            .eq(Apply::getSemeId, semeId)
                            .eq(Apply::getChecked, Constants.APPLY_PASS)
            );
            semesterDeptVo.setStudentNum(studentCount);
            return studentCount != 0;
        }).collect(Collectors.toList());

        // 填充部门名称
        for (SemesterDeptVo semesterDeptVo : semesterDeptVos) {
            Long deptId = semesterDeptVo.getDeptId();
            // 对应的部门名称
            for (SysSimpleDeptVo sysSimpleDeptVo : deptList) {
                if(sysSimpleDeptVo.getDeptId().equals(deptId)) {
                    semesterDeptVo.setDeptName(sysSimpleDeptVo.getDeptName());
                }
            }
        }

        // 分出是否分组的
        for (SemesterDeptVo semesterDeptVo : semesterDeptVos) {
            // 未分组
            Long mergeClassId = semesterDeptVo.getMergeClassId();
            if (mergeClassId == null || mergeClassId == 0) {
                waitDeptList.add(semesterDeptVo);
            // 已经分组
            } else if (mergeClassId <= Constants.MERGE_CLASS_COUNT) {
                // 第几分班
                List<SemesterDeptVo> mergeClass = mergeClassList.get(Math.toIntExact(mergeClassId -1));
                mergeClass.add(semesterDeptVo);
            } else {
                waitDeptList.add(semesterDeptVo);
            }
        }
        return mergeDeptInfo;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveMergeDeptInfo(SaveMergeClassVo saveMergeClassVo) {
        List<Long> deptIds = saveMergeClassVo.getDeptIds();
        Long mergeClassId = saveMergeClassVo.getMergeClassId();
        Long semeId = saveMergeClassVo.getSemeId();
        // 原合班设置为空
        semesterDeptMapper.update(
                null,
                new LambdaUpdateWrapper<SemesterDept>()
                    .set(SemesterDept::getMergeClassId, 0)
                    .eq(SemesterDept::getSemeId, semeId)
                    .eq(SemesterDept::getMergeClassId, mergeClassId)
        );
        if(deptIds == null || deptIds.size() == 0) {
            return;
        }
        // 合班添加班级
        semesterDeptMapper.update(
                null,
                new LambdaUpdateWrapper<SemesterDept>()
                        .set(SemesterDept::getMergeClassId, mergeClassId)
                        .eq(SemesterDept::getSemeId, semeId)
                        .in(SemesterDept::getDeptId, deptIds)
        );
    }

}
